﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Runtime.InteropServices;
//using System.Windows.Forms;
namespace JYoperation.Class
{        
    
    public class MediaOperation
    {
        #region DLLImport
        [DllImport("bass.dll", EntryPoint = "BASS_StreamCreateFile", CharSet = CharSet.Auto)]
        private static extern int BASS_StreamCreateFileUnicode([MarshalAs(UnmanagedType.Bool)] bool A_0, [In, MarshalAs(UnmanagedType.LPWStr)] string A_1, long A_2, long A_3, BASSFlag A_4);
        
        [return: MarshalAs(UnmanagedType.Bool)]
        [DllImport("bass.dll", CharSet = CharSet.Auto)]
        private static extern bool BASS_SetVolume(float volume);
 
        [return: MarshalAs(UnmanagedType.Bool)]
        [DllImport("bass.dll", CharSet = CharSet.Auto)]
        private static extern bool BASS_Init(int A_0, int A_1, BASSInit A_2, IntPtr A_3, IntPtr A_4);

        [return: MarshalAs(UnmanagedType.Bool)]
        [DllImport("bass.dll", CharSet = CharSet.Auto)]
        public static extern bool BASS_ChannelPlay(int handle, [MarshalAs(UnmanagedType.Bool)] bool restart);
        
        public enum BASSFlag
        {
            BASS_AAC_STEREO = 0x400000,
            BASS_AC3_DOWNMIX_2 = 0x200,
            BASS_AC3_DOWNMIX_4 = 0x400,
            BASS_AC3_DOWNMIX_DOLBY = 0x600,
            BASS_AC3_DYNAMIC_RANGE = 0x800,
            BASS_CD_C2ERRORS = 0x800,
            BASS_CD_SUBCHANNEL = 0x200,
            BASS_CD_SUBCHANNEL_NOHW = 0x400,
            BASS_DEFAULT = 0,
            BASS_DSHOW_NOAUDIO_PROC = 0x80000,
            BASS_DSHOW_STREAM_AUTODVD = 0x4000000,
            BASS_DSHOW_STREAM_LOOP = 0x8000000,
            BASS_DSHOW_STREAM_MIX = 0x1000000,
            BASS_DSHOW_STREAM_VIDEOPROC = 0x20000,
            BASS_FX_BPM_BKGRND = 1,
            BASS_FX_BPM_MULT2 = 2,
            BASS_FX_FREESOURCE = 0x10000,
            BASS_MIDI_DECAYEND = 0x1000,
            BASS_MIDI_DECAYSEEK = 0x4000,
            BASS_MIDI_FONT_MMAP = 0x20000,
            BASS_MIDI_NOFX = 0x2000,
            BASS_MIDI_SINCINTER = 0x800000,
            BASS_MIXER_BUFFER = 0x2000,
            BASS_MIXER_DOWNMIX = 0x400000,
            BASS_MIXER_END = 0x10000,
            BASS_MIXER_FILTER = 0x1000,
            BASS_MIXER_LIMIT = 0x4000,
            BASS_MIXER_MATRIX = 0x10000,
            BASS_MIXER_NONSTOP = 0x20000,
            BASS_MIXER_NORAMPIN = 0x800000,
            BASS_MIXER_PAUSE = 0x20000,
            BASS_MIXER_POSEX = 0x2000,
            BASS_MIXER_RESUME = 0x1000,
            BASS_MUSIC_3D = 8,
            BASS_MUSIC_AUTOFREE = 0x40000,
            BASS_MUSIC_DECODE = 0x200000,
            BASS_MUSIC_FLOAT = 0x100,
            BASS_MUSIC_FT2MOD = 0x2000,
            BASS_MUSIC_FX = 0x80,
            BASS_MUSIC_LOOP = 4,
            BASS_MUSIC_MONO = 2,
            BASS_MUSIC_NONINTER = 0x10000,
            BASS_MUSIC_NOSAMPLE = 0x100000,
            BASS_MUSIC_POSRESET = 0x8000,
            BASS_MUSIC_POSRESETEX = 0x400000,
            BASS_MUSIC_PRESCAN = 0x20000,
            BASS_MUSIC_PT1MOD = 0x4000,
            BASS_MUSIC_RAMP = 0x200,
            BASS_MUSIC_RAMPS = 0x400,
            BASS_MUSIC_SINCINTER = 0x800000,
            BASS_MUSIC_STOPBACK = 0x80000,
            BASS_MUSIC_SURROUND = 0x800,
            BASS_MUSIC_SURROUND2 = 0x1000,
            BASS_RECORD_PAUSE = 0x8000,
            BASS_SAMPLE_3D = 8,
            BASS_SAMPLE_8BITS = 1,
            BASS_SAMPLE_FLOAT = 0x100,
            BASS_SAMPLE_FX = 0x80,
            BASS_SAMPLE_LOOP = 4,
            BASS_SAMPLE_MONO = 2,
            BASS_SAMPLE_MUTEMAX = 0x20,
            BASS_SAMPLE_OVER_DIST = 0x30000,
            BASS_SAMPLE_OVER_POS = 0x20000,
            BASS_SAMPLE_OVER_VOL = 0x10000,
            BASS_SAMPLE_SOFTWARE = 0x10,
            BASS_SAMPLE_VAM = 0x40,
            BASS_SPEAKER_CENLFE = 0x3000000,
            BASS_SPEAKER_CENTER = 0x13000000,
            BASS_SPEAKER_FRONT = 0x1000000,
            BASS_SPEAKER_FRONTLEFT = 0x11000000,
            BASS_SPEAKER_FRONTRIGHT = 0x21000000,
            BASS_SPEAKER_LEFT = 0x10000000,
            BASS_SPEAKER_LFE = 0x23000000,
            BASS_SPEAKER_PAIR1 = 0x1000000,
            BASS_SPEAKER_PAIR10 = 0xa000000,
            BASS_SPEAKER_PAIR11 = 0xb000000,
            BASS_SPEAKER_PAIR12 = 0xc000000,
            BASS_SPEAKER_PAIR13 = 0xd000000,
            BASS_SPEAKER_PAIR14 = 0xe000000,
            BASS_SPEAKER_PAIR15 = 0xf000000,
            BASS_SPEAKER_PAIR2 = 0x2000000,
            BASS_SPEAKER_PAIR3 = 0x3000000,
            BASS_SPEAKER_PAIR4 = 0x4000000,
            BASS_SPEAKER_PAIR5 = 0x5000000,
            BASS_SPEAKER_PAIR6 = 0x6000000,
            BASS_SPEAKER_PAIR7 = 0x7000000,
            BASS_SPEAKER_PAIR8 = 0x8000000,
            BASS_SPEAKER_PAIR9 = 0x9000000,
            BASS_SPEAKER_REAR = 0x2000000,
            BASS_SPEAKER_REAR2 = 0x4000000,
            BASS_SPEAKER_REAR2LEFT = 0x14000000,
            BASS_SPEAKER_REAR2RIGHT = 0x24000000,
            BASS_SPEAKER_REARLEFT = 0x12000000,
            BASS_SPEAKER_REARRIGHT = 0x22000000,
            BASS_SPEAKER_RIGHT = 0x20000000,
            BASS_SPLIT_SLAVE = 0x1000,
            BASS_STREAM_AUTOFREE = 0x40000,
            BASS_STREAM_BLOCK = 0x100000,
            BASS_STREAM_DECODE = 0x200000,
            BASS_STREAM_PRESCAN = 0x20000,
            BASS_STREAM_RESTRATE = 0x80000,
            BASS_STREAM_STATUS = 0x800000,
            BASS_UNICODE = -2147483648,
            BASS_WV_STEREO = 0x400000
        }
        
        public enum BASSInit
        {
            BASS_DEVICE_3D = 4,
            BASS_DEVICE_8BITS = 1,
            BASS_DEVICE_CPSPEAKERS = 0x400,
            BASS_DEVICE_DEFAULT = 0,
            BASS_DEVICE_FREQ = 0x4000,
            BASS_DEVICE_LATENCY = 0x100,
            BASS_DEVICE_MONO = 2,
            BASS_DEVICE_NOSPEAKER = 0x1000,
            BASS_DEVICE_SPEAKERS = 0x800,
            BASS_DEVIDE_DMIX = 0x2000
        }
        #endregion
        public int StreamHandle = 0;
        public MediaOperation(string Filename)
        {
            BASS_Init(-1, 44100, BASSInit.BASS_DEVICE_DEFAULT, IntPtr.Zero);
            StreamHandle = BASS_StreamCreateFile(Filename, 0L, 0L, BASSFlag.BASS_DEFAULT);
        }
        /// <summary>
        /// 播放文件
        /// </summary>
        public void play(bool restart)
        {
            BASS_ChannelPlay(StreamHandle, restart);
        }
        private static bool BASS_Init(int device, int freq, BASSInit flags, IntPtr win)
        {
            return BASS_Init(device, freq, flags, win, IntPtr.Zero);
        }
        public void setVolume(float Volume)
        {
            BASS_SetVolume(Volume);
        }

        private static int BASS_StreamCreateFile(string file, long offset, long length, BASSFlag flags)
        {
            flags |= BASSFlag.BASS_DEFAULT | BASSFlag.BASS_UNICODE;
            return BASS_StreamCreateFileUnicode(false, file, offset, length, flags);
        }

        public class MidiOperation
        {
            int steamHandle = 0;
            #region MidiDLLImport
            [Serializable, StructLayout(LayoutKind.Sequential, CharSet=CharSet.Auto)]
            public sealed class BASS_MIDI_FONT
            {
                public int font;            // soundfont
                public int preset;          // preset number (-1=all)
                public int bank;
            }
    
            public enum BassMidiFlag
            {
                BASS_MIDI_NOFX = 0x2000,
                BASS_UNICODE = -2147483648,
                BASS_SAMPLE_LOOP = 4,        //' looped
            }
            [DllImport("bassmidi.dll", EntryPoint = "BASS_MIDI_StreamCreateFile", CharSet = CharSet.Auto)]
            private static extern int BASS_MIDI_StreamCreateFileUnicode(
                [MarshalAs(UnmanagedType.Bool)] bool A_0, 
                //int A_0,
                [In, MarshalAs(UnmanagedType.LPWStr)] string A_1, 
                long A_2, 
                long A_3, 
                BassMidiFlag A_4,
                int A_5);

            [DllImport("bassmidi.dll", CharSet = CharSet.Auto)]
            private static extern int BASS_MIDI_FontInit(
                [In, MarshalAs(UnmanagedType.LPWStr)]string strFileName,
                BassMidiFlag flags);

            [DllImport("bassmidi.dll", CharSet = CharSet.Auto)]
            private static extern int BASS_MIDI_StreamSetFonts(int handle, 
                [In,Out] BASS_MIDI_FONT fonts, 
                int count);

            [DllImport("bassmidi.dll", CharSet = CharSet.Auto)]
            private static extern int BASS_MIDI_StreamGetFonts(int handle,
                [In, Out] BASS_MIDI_FONT fonts,
                int count);
            #endregion
            public void SetFonts()
            {
                int newfont = BASS_MIDI_FontInit(@".\audio\midi\mid.sf2", BassMidiFlag.BASS_UNICODE);
                if (newfont == 1)
                {
                    BASS_MIDI_FONT sf = new BASS_MIDI_FONT();
                    sf.font = newfont;
                    sf.preset = -1; // use all presets
                    sf.bank = 0; // use default bank(s)
                    BASS_MIDI_StreamSetFonts(0, sf, 1);
                }
                //else
                //{
                //    MessageBox.Show("初始化失败");
                //}
            }
            public MidiOperation(string Filename)
            {
                BASS_Init(-1, 44100, BASSInit.BASS_DEVICE_DEFAULT, IntPtr.Zero);
                BASS_MIDI_FONT sf = new BASS_MIDI_FONT();
                BASS_MIDI_StreamGetFonts(0, sf, 1);
                steamHandle = BASS_MIDI_StreamCreateFile(Filename, 0, 0, BassMidiFlag.BASS_SAMPLE_LOOP);
                //if (steamHandle == 0) { MessageBox.Show("读取失败"); };
                SetFonts();
            }
            public void play()
            {
                BASS_ChannelPlay(steamHandle, true);
            }
            private static int BASS_MIDI_StreamCreateFile(string file, long offset, long length, BassMidiFlag flags)
            {
                flags |= BassMidiFlag.BASS_UNICODE;
                return BASS_MIDI_StreamCreateFileUnicode(false, file, offset, length, flags,1);
            }

        }
    }
}
